package org.hcf.common.util;

import lombok.extern.slf4j.Slf4j;

import java.lang.reflect.Field;
import java.security.MessageDigest;

/**
 * MD5工具类
 *
 * @author Alex
 * 2018-09-29 14:59:45
 */
@Slf4j
public class MD5Util {
    private static MessageDigest digest;// = MessageDigest.getInstance("MD5");


    // md5加密字符串时加上尾巴防止爆破
    private static final String TAIL = "!@#BLM123";

    /**
     * md5编码字符串
     *
     * @param s
     * @return
     */
    public static String encodeWithTail(String s) {

        return encode(s + TAIL);
    }

    static MessageDigest getMessageDigest() {
        if (digest == null || !getDigestStatus()) {
            try {
                digest = MessageDigest.getInstance("MD5");
            } catch (Throwable ex) {
                log.error("初始化MD5摘要算法的 MessageDigest 对象异常!!!", ex);
            }
        }
        return digest;
    }

    static boolean getDigestStatus() {
        try {
            Field state = digest.getClass().getField("state");
            state.setAccessible(true);
            return (int) state.get(digest) == 0;
        } catch (Throwable ex) {
        }
        return false;
    }

    /**
     * md5编码字符串
     *
     * @param s
     * @return
     */
    public static String encode(String s) {
        byte[] btInput = s.getBytes();
        // 获得MD5摘要算法的 MessageDigest 对象
        MessageDigest mdInst = getMessageDigest();
        // 使用指定的字节更新摘要
        mdInst.update(btInput);
        // 获得密文
        byte[] md = mdInst.digest();
        return HexUtils.toHex(md);
    }

    public static String encode(byte[] bs) {
        // 获得MD5摘要算法的 MessageDigest 对象
        MessageDigest mdInst = getMessageDigest();
        // 使用指定的字节更新摘要
        mdInst.update(bs);
        // 获得密文
        byte[] md = mdInst.digest();
        // 把密文转换成十六进制的字符串形式
        return HexUtils.toHex(md);
    }
}